OpenAPI定義書レビューの効率化: プルリク時にブランチ名をパスとしたURLでプレビューする
はじめに
OpenAPI定義書のレビュー、どうしていますか?
OpenAPI定義書の修正を含んだコードレビューでは、以下のような方法が一般的かと思います。
- プルリク作成時にyamlのコードを見る
- ローカルでソースを取り込み、VSCodeの拡張機能などでプレビューする
今回は作業の手間を減らすため、プルリク作成時にブランチ名をパスとしたURLでAPI定義書のプレビューが見れる構成を作ってみました。
達成したいイメージ
実際の動作を紹介
1. OpenAPI定義書の修正のプルリクを作成
以下のようなOpenAPI定義書の修正を行い、 ブランチ名 feature/add-users
でプルリクを作成します。
openapi: 3.0.0 info: version: 1.0.0 title: Sample API description: A sample API to illustrate OpenAPI tags: - name: users description: User API paths: /users/{id}: get: tags: - users description: User情報を取得 parameters: - name: id in: path description: User ID required: true schema: type: string example: 80eee574-d798-a7b7-2292-855fa19e8fc5 responses: "200": description: Successful response content: application/json: schema: $ref: "#/components/schemas/User" + /users: + get: + tags: + - users + description: User情報の一覧を取得 + responses: + "200": + description: Successful response + content: + application/json: + schema: + type: array + items: + $ref: "#/components/schemas/User" components: schemas: User: type: object properties: id: type: string description: User ID example: 80eee574-d798-a7b7-2292-855fa19e8fc5 name: type: string description: User Name example: John Doe email: type: string description: User email example: john.doe@example.email.jp age: type: number description: User age example: 21
2. ブランチ名のURLパスにOpenAPI定義書のプレビューが見れる
以下画像のように、ブランチ名のパスでプルリクで修正後のOpenAPI定義書を見ることが出来ます。
3. ブランチ削除後は該当ブランチ名のOpenAPI定義書が削除される
GitHub リポジトリ側の設定で、マージ後に自動でブランチが削除されるようにしておきます。
マージ後ブランチが削除されると、該当のOpenAPI定義書が削除されアクセスできなくなります。
実装
実装についても軽く紹介します。
今回のソースは以下リポジトリにあげてあります。
GitHub Actionsのワークフローの実装
以下の3つを実装しました。
- メインブランチにプッシュされた際にOpenAPI定義書をアップロードする
- プルリク作成時にOpenAPI定義書をアップロードする
- ブランチ削除時にOpenAPI定義書を削除する
こちらのソースを少し解説。プルリク作成時にOpenAPI定義書をアップロードする
ブランチ名のS3にアップロードするGitHub ワークフローの全体です。
name: Upload Open API to S3 with branch name on: pull_request_target: branches: - main paths: - "design/**" jobs: upload-open-api-to-s3: permissions: id-token: write contents: read runs-on: ubuntu-latest defaults: run: working-directory: ./design steps: - uses: actions/checkout@v4 with: ref: ${{ github.head_ref }} - uses: actions/setup-node@v3 with: node-version: 20 - name: Install dependencies run: npm ci - name: Build Open API run: npm run build - name: Configure AWS Credentials uses: aws-actions/configure-aws-credentials@v4 with: role-to-assume: arn:aws:iam::${{ secrets.AWS_ACCOUNT_ID }}:role/${{ secrets.AWS_ROLE_NAME }} aws-region: "${{ vars.AWS_REGION }}" - name: Upload Open API to S3 run: | aws s3 cp ./dist/index.html s3://${{ secrets.S3_BUCKET_NAME }}/${{ github.head_ref }}/index.html
on: pull_request_target: branches: - main paths: - "design/**"
メインブランチへのプルリクのみを対象にします。また、 design
配下に変更があった場合のみ実行するようになっています。
- uses: actions/checkout@v4 with: ref: ${{ github.head_ref }}
actions/checkout@4
でワークフローの作業ブランチを指定しています。
変更したOpenAPI定義書をアップロードしたいので、作業ブランチをプルリク作成側のブランチにしています。
github.head_ref
について: https://docs.github.com/ja/actions/learn-github-actions/contexts#github-context
AWSの構成
CDKでインフラを作成しました。
CloudFront, S3 の一般的な構成です。
こちらも軽く紹介。
import { CloudFrontToS3 } from "@aws-solutions-constructs/aws-cloudfront-s3"; const cloudFrontAndS3 = new CloudFrontToS3(this, "CloudFrontToS3", { bucketProps: { removalPolicy: cdk.RemovalPolicy.DESTROY, }, cloudFrontDistributionProps: { cachePolicy: { defaultTtl: cdk.Duration.seconds(0), }, }, // NOTE: redocから生成されるhtmlが cdnのscript, inline style を使っており、セキュリティヘッダを付与していると弾かれてしまうため無効化 insertHttpSecurityHeaders: false, });
@aws-solutions-constructs/aws-cloudfront-s3
を初めて使ってみました。
その他
- 久しぶりにスナップショットテストを試したいのでついでに入れてみた
- npm workspaces で monorepo 構成を試してみた
- HTML生成をredoc-cliで行っているが、普段 VSCode でSwagger UIを使っているので、そちらで生成してみたかったが方法が分からなかったため断念
- S3のみで静的ウェブサイトホスティングをしてIP制限を掛ける構成でも良かったが、CloudFront FunctionでBasic認証をかけた方が良さそうなので、S3のみでの構成とはしなかった
感想
使った技術に目新しいものは無いですが、GitHub Actions と少し仲良くなれた気がします。
もし利用した方がいたら、感想教えてくれると嬉しいです!